#include "secure_comm.h"
#include <QDebug>  // 调试输出（可根据需求保留/删除，便于排查通信问题）

/**
 * @brief 构造函数：初始化 TCP 服务端，设置基础参数
 */
SecureComm::SecureComm(QObject *parent)
    : QObject(parent)
{
    // 初始化 TCP 服务端（智能指针：无需手动 delete，析构时自动释放内存）
    tcp_server_ = std::make_unique<QTcpServer>(this);

    // 可选：设置服务端最大连接数（根据项目需求调整，0 表示无限制）
    tcp_server_->setMaxPendingConnections(10);  // 示例：最多允许 10 个客户端等待连接
}

/**
 * @brief 析构函数：清理所有资源（关闭服务端、断开客户端）
 */
SecureComm::~SecureComm()
{
    // 1. 关闭 TCP 服务端（停止监听新连接）
    if (tcp_server_ && tcp_server_->isListening()) {
        tcp_server_->close();
        qDebug() << "[SecureComm] TCP server stopped listening";
    }

    // 2. 断开并删除所有已连接的客户端（避免内存泄漏）
    qDeleteAll(client_sockets_);  // 释放客户端 Socket 内存
    client_sockets_.clear();      // 清空客户端列表
    qDebug() << "[SecureComm] All client connections cleaned up";
}

/**
 * @brief 启动 TCP 服务端：监听指定端口
 */
bool SecureComm::startServer(quint16 port)
{
    // 检查 TCP 服务端是否已初始化
    if (!tcp_server_) {
        qCritical() << "[SecureComm] Error: TCP server not initialized";
        return false;
    }

    // 检查服务端是否已在监听（避免重复启动）
    if (tcp_server_->isListening()) {
        qWarning() << "[SecureComm] Warning: TCP server is already listening";
        return true;
    }

    // 启动监听：绑定所有网卡（QHostAddress::Any）+ 指定端口
    if (!tcp_server_->listen(QHostAddress::Any, port)) {
        // 启动失败：输出错误信息（如端口被占用、权限不足）
        qCritical() << "[SecureComm] Failed to start TCP server: " << tcp_server_->errorString();
        return false;
    }

    // 连接信号：新客户端连接时触发 onNewConnection 槽函数
    connect(tcp_server_.get(), &QTcpServer::newConnection,
            this, &SecureComm::onNewConnection);

    // 启动成功：输出调试信息
    qDebug() << "[SecureComm] TCP server started successfully. Listening on port:" << port;
    return true;
}

/**
 * @brief 向指定客户端发送二进制数据
 */
bool SecureComm::sendData(const QByteArray& data, QTcpSocket* clientSocket)
{
    // 检查参数合法性：客户端 Socket 不为空 + 处于连接状态
    if (!clientSocket || clientSocket->state() != QTcpSocket::ConnectedState) {
        qWarning() << "[SecureComm] Failed to send data: Client is not connected";
        return false;
    }

    // 检查数据长度：避免发送空数据（可选，根据项目需求调整）
    if (data.isEmpty()) {
        qWarning() << "[SecureComm] Warning: Trying to send empty data";
        return true;  // 空数据视为“发送成功”（或返回 false，根据需求定义）
    }

    // 发送数据：QTcpSocket::write 返回实际发送的字节数（-1 表示发送失败）
    qint64 bytes_sent = clientSocket->write(data);
    if (bytes_sent == -1) {
        qCritical() << "[SecureComm] Failed to send data: " << clientSocket->errorString();
        return false;
    }

    // 可选：强制刷新缓冲区（确保数据立即发送，避免延迟）
    clientSocket->flush();

    // 发送成功：输出调试信息（数据长度）
    qDebug() << "[SecureComm] Sent" << bytes_sent << "bytes to client";
    return true;
}

/**
 * @brief 获取当前已连接的客户端列表
 */
QList<QTcpSocket*> SecureComm::getConnectedClients() const
{
    return client_sockets_;  // 返回只读列表，避免外部修改内部状态
}

/**
 * @brief 处理新客户端连接：接受连接、绑定信号槽、加入客户端列表
 */
void SecureComm::onNewConnection()
{
    // 获取新连接的客户端 Socket
    QTcpSocket* new_client = tcp_server_->nextPendingConnection();
    if (!new_client) {
        qCritical() << "[SecureComm] Error: Failed to get new client connection";
        return;
    }

    // 修复1：连接“数据接收”信号（语法正确，保留）
    connect(new_client, 
            &QTcpSocket::readyRead,    // 信号：客户端有数据可读
            this, 
            &SecureComm::onReadyRead); // 槽函数：处理数据接收

    // 修复2：连接“客户端断开”信号（语法正确，保留）
    connect(new_client, 
            &QTcpSocket::disconnected, // 信号：客户端断开连接
            this, 
            &SecureComm::onDisconnected); // 槽函数：处理断开逻辑

    // 修复3：连接“客户端错误”信号（关键：补充逗号、整理括号，解决语法错误）
    connect(new_client, 
            &QTcpSocket::errorOccurred, // 信号：客户端发生错误
            [new_client](QAbstractSocket::SocketError err) { // 匿名槽函数（注意逗号）
                // 使用 err 参数，消除“未使用参数”警告
                qWarning() << "[SecureComm] Client error (code:" << err << "): " 
                           << new_client->errorString();
            }); // 修复：确保匿名函数括号闭合，且与 connect 右括号匹配

    // 将新客户端加入列表并发送信号
    client_sockets_.append(new_client);
    emit clientConnected(new_client);

    // 调试输出
    qDebug() << "[SecureComm] New client connected: " << new_client->peerAddress().toString() 
             << ":" << new_client->peerPort();
}

/**
 * @brief 处理客户端数据接收：读取数据并发送信号给外部
 */
void SecureComm::onReadyRead()
{
    // 获取发送数据的客户端（sender() 返回触发信号的对象指针，需强转为 QTcpSocket）
    QTcpSocket* client = qobject_cast<QTcpSocket*>(sender());
    if (!client || !client_sockets_.contains(client)) {
        qWarning() << "[SecureComm] Error: Received data from unknown client";
        return;
    }

    // 读取客户端发送的所有数据（QTcpSocket::readAll 读取缓冲区所有数据）
    QByteArray received_data = client->readAll();

    // 输出调试信息：接收的数据长度和客户端信息
    qDebug() << "[SecureComm] Received" << received_data.size() << "bytes from client"
             << client->peerAddress().toString() << ":" << client->peerPort();

    // 发送信号：将接收的数据传递给外部（如 RobotSystem 处理指令）
    emit dataReceived(received_data, client);
}

/**
 * @brief 处理客户端断开连接：从列表移除、释放内存、发送信号
 */
void SecureComm::onDisconnected()
{
    // 获取断开连接的客户端
    QTcpSocket* client = qobject_cast<QTcpSocket*>(sender());
    if (!client) {
        qWarning() << "[SecureComm] Error: Disconnected signal from unknown source";
        return;
    }

    // 记录客户端信息（用于调试输出）
    QString client_info = QString("%1:%2").arg(client->peerAddress().toString())
                                          .arg(client->peerPort());

    // 从客户端列表移除（避免后续操作已断开的客户端）
    if (client_sockets_.contains(client)) {
        client_sockets_.removeOne(client);
    }

    // 释放客户端 Socket 内存（QTcpSocket::deleteLater 延迟删除，避免信号槽冲突）
    client->deleteLater();

    // 发送信号：通知外部“客户端已断开”
    emit clientDisconnected(client);

    // 输出调试信息
    qDebug() << "[SecureComm] Client disconnected:" << client_info 
             << "Remaining clients:" << client_sockets_.size();
}